package net.scdx.hotel.controller;

import com.spatial4j.core.context.SpatialContext;
import com.spatial4j.core.distance.DistanceUtils;
import com.spatial4j.core.shape.Rectangle;
import net.scdx.hotel.Util.DistanceUtil;
import net.scdx.hotel.Util.NumberUtil;
import net.scdx.hotel.entity.Hotel;
import net.scdx.hotel.entity.User;
import net.scdx.hotel.service.HotelService;
import org.apache.ibatis.annotations.Param;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import sun.util.resources.cldr.ar.CalendarData_ar_QA;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

@Controller
@RequestMapping("/")
public class IndexController {

    @Autowired
    private HotelService hotelService;

    @RequestMapping("/")
    public String index(Hotel hotel, HttpServletRequest request) {
        try {
            if (hotel == null)
                hotel = new Hotel();
            String pageIndexStr = request.getParameter("pageIndex");
            String checktimeStr = request.getParameter("checktime");
            System.out.println("checktime = " + checktimeStr);
            Date checkinTime = null;
            Date checkoutTime = null;

            if (checktimeStr != null && checktimeStr.length() != 23)
                checktimeStr = null;
            try {
                if (checktimeStr != null && checktimeStr.trim() != "") {
                    checkinTime = new Date(checktimeStr.substring(0,10).replaceAll("-","/"));
                    checkoutTime = new Date(checktimeStr.substring(13).replaceAll("-","/"));
                    System.out.println("checkinTime = " + checkinTime);
                    System.out.println("checkoutTime = " + checkoutTime);
                }
            } catch (Exception e) {
                e.printStackTrace();
                checktimeStr = null;
                checkinTime = checkoutTime = null;
            }

            String location = request.getParameter("location");
            if (location==null)  location = "";
            if (location!= null && location.indexOf("=")==-1) location = "";
            Float lon = null,lat = null;
            String distance = request.getParameter("distance");
            if (distance==null) distance = "";
            if (distance!=null&& NumberUtil.isNumeric(distance)==false) distance = "";

            if (location!=null&&location.trim()!="") {
                lon = Float.parseFloat(location.split("=")[0]);
                lat = Float.parseFloat(location.split("=")[1]);
            }

            String minLong,maxLong,minLat,maxLat;

            minLat = minLong = maxLong = maxLat = null;

            if (location!=null&&location.trim()!=""&&distance!=null &&distance.trim()!= "") {
                double radius = Integer.parseInt(distance) / 1000;
                SpatialContext geo = SpatialContext.GEO;
                Rectangle rectangle = geo.getDistCalc().calcBoxByDistFromPt(
                        geo.makePoint(lon, lat), radius * DistanceUtils.KM_TO_DEG, geo, null);
                minLong = String.valueOf(rectangle.getMinX());
                maxLong = String.valueOf(rectangle.getMaxX());
                minLat  = String.valueOf(rectangle.getMinY());
                maxLat  = String.valueOf(rectangle.getMaxY());
            }

            if (pageIndexStr == null)
                pageIndexStr = "1";
            int pageIndex = Integer.parseInt(pageIndexStr);
            if (pageIndex < 1)
                pageIndex = 1;
            if (hotel != null && hotel.getHotelLevel() != null && hotel.getHotelLevel().equals(0))
                hotel.setHotelLevel(null);

            String hotelName =  hotel.getHotelName();
            hotel.setHotelDesc(hotelName);
            hotel.setHotelLocation(hotelName);

            List<Hotel> hotels;

            if (maxLong != null && maxLat != null && minLat != null && minLong != null)
                hotels = hotelService.queryHotelsByDistance(hotel, pageIndex, 12, maxLong,minLong,maxLat,minLat,checkinTime,checkoutTime);
            else
                hotels = hotelService.queryHotels(hotel, pageIndex, 12,checkinTime,checkoutTime);

            List<String> distances = new ArrayList<>();

            if (lon != null && lat != null && maxLong!=null) {
                try {
                    for (Hotel _hotel : hotels) {
                        distances.add(DistanceUtil.algorithm(
                                lon,
                                lat,
                                Float.parseFloat(_hotel.getHotelLongtitude()),
                                Float.parseFloat(_hotel.getHotelLatitude())
                                )
                        );
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                    distances = new ArrayList<>();
                }
            }

            while (distances.size() < hotels.size())
                distances.add("");

            Integer l =hotel.getHotelLevel();
            String n = hotel.getHotelName();
            if (l == null || l < 0 || l > 5)
                l = 0;
            if (n == null || n.trim()=="" || n.trim() == "null")
                n = "";
            request.setAttribute("checktime", checktimeStr);
            request.setAttribute("location", location);
            request.setAttribute("distance", distance);
            request.setAttribute("level", l);
            request.setAttribute("name", n);
            request.setAttribute("size", hotels.size());
            request.setAttribute("hotels", hotels);
            request.setAttribute("distances", distances);
            request.setAttribute("pageIndex", pageIndex);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "index";
    }

    @RequestMapping("/info")
    public String info(HttpSession session) {
        return "info";
    }
}
